package com.conference.service.impl;

import com.conference.entity.ConferenceVenue;
import com.conference.repository.ConferenceVenueRepository;
import com.conference.service.ConferenceVenueService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.persistence.criteria.Predicate;
import java.util.ArrayList;
import java.util.List;
@Service
public class ConferenceVenueServiceImpl implements ConferenceVenueService {

    @Autowired
    private ConferenceVenueRepository venueRepository;

    @Override
    public long getTotalVenues() {
        return venueRepository.countDistinctVenues();
    }

    @Override
    @Transactional
    public ConferenceVenue createVenue(ConferenceVenue venue) {
        return venueRepository.save(venue);
    }

    @Override
    @Transactional
    public ConferenceVenue updateVenue(ConferenceVenue venue) {
        return venueRepository.save(venue);
    }

    @Override
    @Transactional
    public void deleteVenue(Long id) {
        venueRepository.deleteById(id);
    }

    @Override
    public ConferenceVenue getVenueById(Long id) {
        return venueRepository.findById(id).orElse(null);
    }

    @Override
    public List<ConferenceVenue> getVenuesByConferenceId(Long conferenceId) {
        return venueRepository.findByConferenceId(conferenceId);
    }

    @Override
    public Page<ConferenceVenue> searchVenues(Long conferenceId, String venueName, Pageable pageable) {
        return venueRepository.findAll((Specification<ConferenceVenue>) (root, query, cb) -> {
            List<Predicate> predicates = new ArrayList<>();

            if (conferenceId != null) {
                predicates.add(cb.equal(root.get("conferenceId"), conferenceId));
            }

            if (venueName != null && !venueName.isEmpty()) {
                predicates.add(cb.like(cb.lower(root.get("venueName")), "%" + venueName.toLowerCase() + "%"));
            }

            return cb.and(predicates.toArray(new Predicate[0]));
        }, pageable);
    }
} 